<template>
  <div class="page">
    <el-row>
      <el-col :span="4">
        <div class="components-title">
          <i class="iconfont">&#xe85e;</i>
          表格字段
        </div>
        <div class="components-body" @click="transformationForm('portComponents')">
          <span>接口属性</span>
        </div>
        <div class="components-body" style="margin-top: 4px;" @click="transformationForm('tableComponents')">
          <span>表格属性</span>
        </div>
        <draggable v-if="portInfo" v-model="portInfo.dropCol" @start="onStart" @end="onEnd" :animation="property.drag.speed">
          <div v-for="(item, index) in portInfo.dropCol" :key="index" class="components-item">
            <div class="components-body" @click="transformationForm('columnComponents', item)">
              <i class="iconfont">&#xe614;</i>
              {{ item.label || item.prop }}
            </div>
          </div>
        </draggable>
      </el-col>
      <el-col :span="14" style="padding: 10px;">
        <el-table
          v-if="tableInfo"
          :data="portInfo.tableData"
          :height="tableInfo.height"
          :align="tableInfo.align"
          :border="tableInfo.border"
          :header-cell-style="cellStyle"
          :cell-style="cellStyle"
        >
          <el-table-column
            v-for="(item, index) in portInfo.dropCol"
            :key="`col_${index}`"
            :prop="item.prop"
            :label="item.label"
            :width="item.width || ''"
            :show-overflow-tooltip="item.showOverflowTooltip"
            :align="tableInfo.align"
            :formatter="(a, b, c) => filtering(c, item.timeFilte, item.dictFilte)"
          />
        </el-table>
      </el-col>
      <el-col :span="6" class="col-right" style="padding: 10px;">
        <el-form class="el_form" ref="form" :model="formData" label-width="100px" label-position="right">
          <div v-for="item in formList" :key="`form_${item.__bind__}`">
            <el-form-item v-if="item.__type__ === 'input'" :label="item.__title__">
              <el-input style="width: 80%;" v-model="formData[item.__bind__]" :disabled="item.disabled || false" :placeholder="item.placeholder || ''" />
            </el-form-item>
            <el-form-item v-if="item.__type__ === 'textarea'" :label="item.__title__">
              <el-input style="width: 80%;" v-model="formData[item.__bind__]" type="textarea" :placeholder="item.placeholder || ''"></el-input>
            </el-form-item>
            <el-form-item v-if="item.__type__ === 'select'" :label="item.__title__">
              <el-select style="width: 80%;" v-model="formData[item.__bind__]" :placeholder="item.placeholder || ''">
                <el-option v-for="(opt, index) in item.options" :key="`${opt.value}_${index}`" :label="opt.label" :value="opt.value"></el-option>
              </el-select>
            </el-form-item>
            <el-form-item v-if="item.__type__ === 'boole'" :label="item.__title__">
              <el-switch v-model="formData[item.__bind__]" />
            </el-form-item>
            <el-form-item v-if="item.__type__ === 'button'">
              <el-button :type="item.style.type || ''" :icon="item.style.icon || ''" @click="dispatchingEvents(item.event, formData)"
                >{{ item.__title__ }}
              </el-button>
            </el-form-item>
          </div>
        </el-form>
      </el-col>
    </el-row>
  </div>
</template>

<script>
import draggable from 'vuedraggable'
import { $http } from '@/table-generator/utils/request'
import { portComponents, tableComponents, columnComponents } from '@/table-generator/utils/config'
import _formList from '@/table-generator/utils/formList'
import { getDataByPath } from '@/table-generator/utils/public'
import { getPage1 } from '@/api/test'

export default {
  name: 'Index',
  components: { draggable },
  data() {
    return {
      // 页面使用属性
      property: {
        // 拖拽
        drag: {
          speed: 300 // 动画速度
        }
      },
      // 接口属性
      portInfo: null,
      // 表格属性
      tableInfo: null,
      // 高亮组件
      cellHighlight: {
        type: null,
        prop: null
      },
      // 高亮组件表单
      formList: {},
      formData: {}
    }
  },
  mounted() {
    this.init()
    console.log('加载完成', getPage1())
  },
  methods: {
    /**
     * 周期--初始化
     */
    init() {
      this.portInfo = Object.assign({}, portComponents) // 接口数据
      this.tableInfo = Object.assign({}, tableComponents) // 表格数据
      console.log(this.tableInfo)
    },
    /**
     * 左边--选择不同模块，获取表单属性
     */
    transformationForm(type, item) {
      if (!type) {
        console.error('【type为必选参数】')
        return
      }
      const formList = Object.assign({}, _formList[type])
      // 接口表单
      if (type === 'portComponents') {
        if (this.cellHighlight.type === type) {
          this.cellHighlight = {
            type: null,
            prop: null
          }
        } else {
          this.cellHighlight = {
            type: type,
            prop: ''
          }
          this.formList = formList
          this.formData = this.portInfo
          this.tableInfo.height = ''
        }
      }
      // 表格数据点击
      if (type === 'tableComponents') {
        if (!this.portInfo.tableData.length) {
          this.$message.error('表格无数据')
          return
        }
        this.formList = formList
        this.formData = this.tableInfo
      }
      // 表格列
      if (type === 'columnComponents') {
        if (this.cellHighlight.prop === item.prop) {
          this.cellHighlight = {
            type: null,
            prop: null
          }
          this.formList = []
          this.formData = {}
        } else {
          this.cellHighlight = {
            type: type,
            prop: item.prop
          }
          this.formList = formList
          this.formData = item
        }
      }
    },
    /**
     * 中间--单元格样式
     * @param columnIndex
     */
    cellStyle({ column }) {
      if (this.cellHighlight.type === 'columnComponents') {
        if (this.cellHighlight.prop === column.property) {
          return {
            'background-color': '#67C23A',
            color: '#ffffff'
          }
        }
      }
    },
    /**
     * 右边--事件分发
     */
    dispatchingEvents(event, item) {
      this[event](item)
    },
    /**
     * 被分发--根据条件加载数据
     */
    getData() {
      // const res = getPage1() // 模拟获取后台数据
      let portInfo = this.portInfo
      if (!portInfo.mockMode) {
        this.$message.error('请选择模式')
        return
      }
      let mockParameter = null
      if (portInfo.mockParameter) {
        try {
          mockParameter = JSON.parse(portInfo.mockParameter)
        } catch (e) {
          this.$message.error('入参解析错误')
          return
        }
      }
      let mockHeader = null
      if (portInfo.mockHeader) {
        try {
          mockHeader = JSON.parse(portInfo.mockHeader)
        } catch (e) {
          this.$message.error('header解析错误')
          return
        }
      }
      if (!portInfo.codePath || !portInfo.codeNorm || !portInfo.dataPath) {
        this.$message.error('请填写必填参数')
        return
      }
      $http(portInfo.mockMode, portInfo.url, mockParameter || '', mockHeader || '')
        .then(res => {
          console.log('接口回调', res)
          const code = getDataByPath(res, portInfo.codePath)
          if (Number(code) !== Number(portInfo.codeNorm)) {
            this.$message.error('状态码不匹配，请检查接口')
          } else {
            const data = getDataByPath(res, portInfo.dataPath)
            if (!Array.isArray(data)) {
              this.$message.error('数据集不是数组，请检查接口')
            } else {
              if (!data.length) {
                this.$message.error('数据长度为0，请检查接口')
              } else {
                let dropCol = []
                for (const e in data[0]) {
                  dropCol.push(
                    Object.assign({}, columnComponents, {
                      prop: e,
                      label: e
                    })
                  )
                }
                portInfo.dropCol = dropCol
                portInfo.tableData = data
                if (portInfo.totalPath) {
                  const total = getDataByPath(res, portInfo.totalPath)
                  if (total) portInfo.total = total
                }
              }
            }
          }
        })
        .catch(err => {
          this.$message.error('接口异常，请查看控制台')
          console.log('【异常信息】', err)
        })
    },
    /**
     * 被分发--删除当前字段
     */
    deleteCol(item) {
      this.$utils.remove(this.table.dropCol, e => e.prop === item.prop)
    },
    /**
     * 数据过滤器
     * @param value
     * @param timeFilte
     * @param dictFilte
     * @returns {string}
     */
    filtering(value, timeFilte = '', dictFilte = '') {
      if (typeof value === 'string') {
        // 时间过滤
        if (timeFilte) {
          if (!new Date(value).getTime()) {
            return '时间格式不标准'
          } else {
            return this.$moment(value).format(timeFilte)
          }
        }
        // 字典过滤
        if (dictFilte) {
          try {
            const obj = JSON.parse(dictFilte)
            return obj[value]
          } catch (e) {
            return 'json格式不正确'
          }
        }
        return value
      } else {
        return '不是字符串'
      }
    },
    onStart(e) {
      console.log('开始拖动', e)
    },
    onEnd(e) {
      console.log('结束拖动', e)
    }
  }
}
</script>

<style lang="scss" scoped>
@import '../table-generator/icon/aliIcon.css';

@import '../components/table-generator/css/home';

.components-item {
  display: inline-block;
  width: 48%;
  margin: 1%;
  transition: transform 0ms !important;
}

.col-right {
  .el_form {
    ::v-deep input {
      height: 30.5px;
      line-height: 30.5px;
    }
  }
}
</style>
